<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>自定义指令</title>
    <script src="https://cdn.jsdelivr.net/npm/vue@2/dist/vue.js"></script>
</head>

<body>

    <div id="app">
        <h1>{{msg}}</h1>

        <div v-text="msg"></div>
        <!-- 自定义指令 text-danger -->
        <div v-text-danger="msg"></div>

        用户名：<input type="text" v-bind="username">
        <!-- 
            需要一个指令，可以和v-bind指令完成相同的功能，同时将该元素的父级元素的背景色改为蓝色
        -->
        <div>
            用户名：<input type="text" v-bind-blue="username">
        </div>
    </div>

    <hr />

    <!-- 此处为全局的自定义指令 -->
    <div id="app2">
        <div v-text-green="msg"></div>
        <div>
            用户名：<input type="text" v-bind-yellow="username">
        </div>
    </div>

    <script>

        const vm = new Vue({
            el: '#app',
            data: {
                msg: '自定义指令',
                username: 'zhangsan'
            },
            directives: {
                //指令1
                //指令2
                //...
                //关于这个指令的名字：1.“v-”不需要写；2.Vue官方建议指令的名字全部小写，如果是多个单词的话，请使用 - 进行链接
                //这个回调函数的执行时机包括两个：1.标签和指令第一次绑定的时候；2.模板被重新解析的时候
                //这个回调函数有两个参数：1.真实的dom元素“element”；2.标签和指令之间绑定关系的对象“binding”
                //这种方式属于函数式方式
                'text-danger': function (element, binding) {
                    console.log('window', this) //自定义指令的方法里面的this指的是window
                    console.log('element', element)
                    console.log('binding', binding)
                    element.innerText = binding.value
                    element.style.color = 'red'
                },
                /*
                'bind-blue': function (element, binding) {
                    console.log('element', element)
                    console.log('binding', binding)

                    element.value = binding.value
                    // 为什么是null，原因是这个函数在执行的时候，指令和元素完成了绑定，但仅是在内存中完成了绑定，元素没有被插入到页面中
                    console.log('parentNode', element.parentNode)
                    element.parentNode.style.backgroundColor = 'blue'  //错误
                }
                */

                //对象式
                'bind-blue': {
                    //这个对象中三个方法的名字不能随便写
                    //这三个函数将来都会被自动调用
                    //注意：在特定的时间节点调用特定的函数，这种被调用的函数成为钩子函数

                    //元素与指令初次绑定的时候，自动调用bind
                    bind(element, binding) {
                        console.log('window', this) //自定义指令的方法里面的this指的是window
                        element.value = binding.value
                    },
                    //元素被插入到页面之后，这个函数被自动调用
                    inserted(element, binding) {
                        element.parentNode.style.backgroundColor = 'blue'
                    },
                    //当模板重新解析的时候，这个函数会被自动调用
                    update(element, binding) {
                        element.value = binding.value
                    }

                }

            }
        })



        //定义全局的自定义指令
        //1.函数式
        Vue.directive('text-green', function (element, binding) {
            console.log('window', this) //自定义指令的方法里面的this指的是window
            element.innerText = binding.value
            element.style.color = 'green'
        })
        //2.对象式
        Vue.directive('bind-yellow', {
            //元素与指令初次绑定的时候，自动调用bind
            bind(element, binding) {
                console.log('window', this) //自定义指令的方法里面的this指的是window
                element.value = binding.value
            },
            //元素被插入到页面之后，这个函数被自动调用
            inserted(element, binding) {
                element.parentNode.style.backgroundColor = 'yellow'
            },
            //当模板重新解析的时候，这个函数会被自动调用
            update(element, binding) {
                element.value = binding.value
            }
        })

        const vm2 = new Vue({
            el: '#app2',
            data: {
                msg: '全局自定义指令',
                username: '李四'
            },
        })

    </script>

</body>

</html>